home *** CD-ROM | disk | FTP | other *** search
/ Collection of Tools & Utilities / Collection of Tools and Utilities.iso / turbovis / tvtool17.zip / ACTLIB.ZIP / TOOLS.ZIP / TESTDRV.C < prev    next >
C/C++ Source or Header  |  1993-10-12  |  4KB  |  173 lines

  1. /*  Copyright (C) 1993   Marc Stern  (internet: stern@mble.philips.be)  */
  2.  
  3. #include "tools.h"
  4. #include "bool.h"
  5. #include <bios.h>
  6. #include <fcntl.h>
  7. #include <sys\types.h>  /* for Microsoft: always sys\types.h before sys\stat.h */
  8. #include <sys\stat.h>
  9. #include <errno.h>
  10.  
  11.  
  12.  
  13. static int diskError;
  14.  
  15.  
  16. /* interrupt function pointer */
  17. typedef void interrupt (*fptr)();
  18.  
  19. fptr oldHandler;
  20.  
  21.  
  22. /* For interrupt */
  23. #if defined(__TURBOC__)
  24. # pragma warn -par
  25. # pragma warn -rvl
  26. #endif
  27.  
  28. int myHandler( int errval, int axp, int bpp, int sip )
  29. {
  30.  _enable();
  31.  
  32. #if 0
  33.  if ( ax < 0 )   /*  not a disk error  */
  34.     {
  35.      _AX = ax;
  36.      _DI = errval;
  37.      _BP = bp;
  38.      _SI = si;
  39.      oldHandler();
  40.      hardretn( _HARDERR_ABORT );
  41.     }
  42. #endif
  43.  
  44.  diskError = LOWBYTE( errval );
  45.  
  46.  hardretn( _HARDERR_FAIL );
  47. }
  48.  
  49. #if defined(__TURBOC__)
  50. # pragma warn .par
  51. # pragma warn .rvl
  52. #endif
  53.  
  54.  
  55. /***
  56.  *
  57.  *  Function   :    test_drive
  58.  *
  59.  *  Topics     :    Test the availability of a drive.
  60.  *
  61.  *  Parameters :    in    int drive         0 = A:, 1 = B:, 2 = C:,...
  62.  *
  63.  *  Return code:    combination (bitwise OR) of
  64.  *                  D_READABLE
  65.  *                  D_WRITEABLE
  66.  *                  D_NOFORMAT
  67.  *                  D_INVALID
  68.  *                  D_NOTINSERTED
  69.  *                  D_REMOVABLE
  70.  *                  D_SUBST
  71.  *                  D_REMOTE
  72.  *                  D_RAM
  73.  *
  74.  *  OS/Compiler :   MS-DOS version >= 3.10
  75.  ***/
  76.  
  77. int test_drive( int drive )
  78. {
  79.  char fname[] = "x:\\t.t";
  80.  int fhandle, status = 0;
  81.  
  82. #define INTR 0x24
  83.  /* save the old Fatal Error Interrupt handler */
  84.  oldHandler  = _dos_getvect( INTR );
  85.  
  86.  /* install new Fatal Error Interrupt handler */
  87.  harderr( myHandler );
  88.  
  89.  diskError = -1;
  90.  
  91.  /* Open a file (write) */
  92.  *fname = drive + 'A';
  93.  fhandle = open( fname, O_CREAT, S_IREAD|S_IWRITE );
  94.  
  95.  /* restore the old Fatal Error Interrupt handler */
  96.  _dos_setvect( INTR, oldHandler );
  97.  
  98.  if ( fhandle >= 0 )
  99.     {
  100.      close( fhandle );
  101.      unlink( fname );
  102.     }
  103.  else if ( diskError < 0 ) diskError = _doserrno + 256;
  104.  
  105.  switch( diskError )
  106.  {
  107.   case -1: status |= D_WRITEABLE;
  108.  
  109.   case EACCES + 256:
  110.   case  0: status |= D_READABLE; break;
  111.  
  112.   /*case EINVFMT + 256:*/
  113.   case 0x07:
  114.   case 0x0C: status |= D_NOFORMAT; break;
  115.  
  116. #if 0
  117.   case ENMFILE + 256: /* No more files */
  118.   case EMFILE  + 256: /* Too many open files */
  119.   case ENOENT  + 256: /* No such file or directory*/
  120.   case ENOPATH + 256: /* Path not found           */
  121. #endif
  122.   default: status = D_INVALID;
  123.  }
  124.  
  125.  {
  126.  union REGS regs;
  127.  
  128.  /*  Test if drive is remote, subst  */
  129.  regs.h.ah = 0x44;    /* IOCTL function   */
  130.  regs.h.al = 0x09;    /* subfunction  */
  131.  regs.h.bl = drive + 1;
  132.  intdos( ®s, ®s );
  133.  if ( ! regs.x.cflag )
  134.     {
  135.      if ( regs.x.dx & 0x8000 ) status |= D_SUBST;
  136.      if ( regs.x.dx & 0x1000 ) status |= D_REMOTE;
  137.     }
  138.  
  139. /*  Test if drive is removable  */
  140.  regs.h.ah = 0x44;    /* IOCTL function   */
  141.  regs.h.al = 0x08;    /* subfunction  */
  142.  regs.h.bl = drive + 1;
  143.  intdos( ®s, ®s );
  144.  if ( ! regs.x.cflag )
  145.     if ( regs.x.ax == 0 ) status |= D_REMOVABLE;
  146.  }
  147.  
  148. /*  Test if drive is a RAM disk  */
  149.  if ( status & D_READABLE )
  150.     {
  151.      union REGS regs;
  152.      struct SREGS sregs;
  153.      unsigned char far *fat_nb;
  154.  
  155.      regs.h.ah = 0x32;    /* IOCTL function   */
  156.      regs.h.dl = drive + 1;
  157.      intdosx( ®s, ®s, &sregs );
  158. //     if ( regs.h.al ) status |= D_INVALID;
  159.      fat_nb = MK_FP( sregs.ds, regs.x.bx + 8 );
  160.      if ( *fat_nb == 1 )
  161.         status |= D_RAM;
  162.     }
  163.  
  164.  /* Test if disk inserted */
  165.  if ( (status & D_INVALID) && (status & D_REMOVABLE) )
  166.     {
  167.      status |= D_NOTINSERTED;
  168.      status &= ~D_INVALID;
  169.     }
  170.  
  171.  return status;
  172. }
  173.